// 一个越转越慢地转盘
// 模式：建造者模式 / 函数式
// 获取最终奖品，开始转动，每转一圈减慢速度，最后一圈停在对应奖品上。
// 结果模块，动画效果模块，转动控制模块，html结构生成模块
// 单一职责原则：分模块，方便改动
let observe = {
  message: {},
  regist: function (type, fn) {
    this.message[type] = fn;
  },
  fire: function (type) {
    this.message[type]();
  },
  unregist: function (type) {
    delete this.message[type];
  },
};
let _domArr = []; // 方便dom操作
// html结构生成模块
function htmlInit(target) {
  for (let i = 0; i < 10; i++) {
    // 假设有十个奖品
    let _div = document.createElement("div");
    _div.setAttribute("class", "item");
    _div.innerHtml = i;
    target.appendChild(_div);
    _domArr.push(_div); // 存下dom
  }
}
// 结果模块
function getFinal() {
  let _num = Math.random() * 10 + 40; // 可用api代替，40表示基础4圈
  return Math.floor(_num, 0);
}
// 动画效果模块
function mover(moveConfig = { moveTime: 10, speed: 20 }) {
  let nowIn = 0; // 当前格序号
  let removeNum = 9; // 当前需移除格序号
  let timer = setInterval(() => {
    if (nowIn !== 0) {
      removeNum = 9;
    }
    _domArr[removeNum].setAttribute("class", "item");
    _domArr[removeNum].setAttribute("class", "item item-on");
    nowIn++;
    if (nowIn === moveConfig.moveTime) {
      clearInterval(timer);
      if (moveConfig.moveTime === 10) {
        // 转完了
        observe.fire("finish");
      }
    }
  }, moveConfig.speed);
}
// 转动控制模块
function moveControl() {
  let final = getFinal();
  let _circle = Math.floor(final / 10, 0); // 取整，基础动画圈
  let _runCircle = 0; // 已经跑了几圈
  let _stopNum = final % 10; // 最终停在哪格
  let _speed = 200; // 初始速度 ms
  mover({
    moveTime: 10, // 移动几格
    speed: _speed,
  });
  observe.regist("finish", function () {
    let _time = 0;
    _speed -= 50;
    _runCircle++;
    if (_runCircle <= _circle) {
      // 还没转完基础圈
      _time = 10;
    } else {
      // 最终圈
      _time = _stopNum;
    }
    mover({
      moveTime: _time,
      speed: _speed,
    });
  });
}
function begin() {
  htmlInit(document.getElementById("#app"));
  moveControl();
}
window.begin = begin;

// 例1：加工水果罐头：切水果 => 消毒部门 => 加糖 => 装瓶 => 装箱
// 例2：axios
// 例3：验证输入：事件绑定模块 => 前端验证模块 => 后端验证模块
input.onblur = function () {
  let _value = input.value;
  let _arr = [front, back]; // [front,middle,back]
  async function test() {
    // back为异步
    let _result = _value;
    while (_arr.length > 0) {
      // 依次执行_arr里的每一个方法，然后把上一个方法的结果给到下一个（类似axios源码）
      _result = await _arr.shift()(_result);
    }
  }
  test().then((res) => {
    // 操作结果
  });
};
// 前端验证模块
function front() {}
// 后端验证模块
function back() {}

// 可扩展性强：后期若突然增加一个终端验证，只需要增加一个middle方法，加入职责链中
